package com.ray.test.serializable;

import com.dyuproject.protostuff.LinkedBuffer;
import com.dyuproject.protostuff.ProtobufIOUtil;
import com.dyuproject.protostuff.Schema;
import com.dyuproject.protostuff.runtime.RuntimeSchema;
import com.ray.test.proxy.MockData;
import com.ray.test.proxy.MockTestConfig;
import lombok.extern.slf4j.Slf4j;
import org.springframework.util.FileCopyUtils;

import java.io.File;
import java.io.IOException;

/**
 * @author bo shen
 * @Description: protostuff 序列化
 * @Class: ProtostuffSerializable
 * @Package com.ray.test.serializable
 * @date 2019/12/20 8:50
 * @company <p>杭州传化陆鲸科技有限公司</p>
 * @updateRecord time(修改时间)  author(修改人)   desc(修改内容)
 */
@Slf4j
public class ProtostuffSerializable implements Serializable {
    /**
     * 文件后缀
     **/
    private String fileType = ".mock";

    @Override
    public void set(MockTestConfig config) {
        MockData mockData = config.getMockData();
        Schema schema = RuntimeSchema.getSchema(mockData.getClass());
        byte[] data = ProtobufIOUtil.toByteArray(mockData, schema,
                LinkedBuffer.allocate(LinkedBuffer.DEFAULT_BUFFER_SIZE));
        try {
            log.info("文件保存地址:{}", config.getSourcePath() + fileType);
            File file = new File(config.getSourcePath() + fileType);
            if (file.exists()) {
                file.delete();
            }
            File fileParent = file.getParentFile();
            //首先创建父类文件夹
            if (!fileParent.exists()) {
                fileParent.mkdirs();
            }
            file.createNewFile();
            FileCopyUtils.copy(data, file);
        } catch (IOException e) {
            log.info("文件保存失败", e);
            throw new RuntimeException("文件保存失败");
        } catch (Exception e) {
            log.info(e.getMessage());
            throw new RuntimeException("可能数据结构发生变化,数据无法序列化");
        }
    }

    @Override
    public MockTestConfig get(MockTestConfig config) {
        try {
            File file = new File(config.getFilePath() + fileType);
            if (!file.exists()) {
                return config;
            }
            byte[] data = FileCopyUtils.copyToByteArray(file);
            MockData mockData = new MockData();
            Schema schema = RuntimeSchema.getSchema(mockData.getClass());
            ProtobufIOUtil.mergeFrom(data, mockData, schema);
            config.setHasData(true);
            config.setReflush(false);
            config.setMockData(mockData);
        } catch (IOException e) {
            log.info("文件读取失败", e);
            throw new RuntimeException("文件读取失败");
        } catch (Exception e) {
            log.info(e.getMessage());
            throw new RuntimeException("可能数据结构发生变化,数据无法反序列化");
        }
        return config;
    }

    @Override
    public void deleteFile(MockTestConfig config) {
        log.info("文件删除地址:{}", config.getSourcePath() + fileType);
        File file = new File(config.getSourcePath() + fileType);
        if (file.exists()) {
            file.delete();
        }
    }
}
